#include "my_libproc.h"

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
#include <stdint.h>
#include <time.h>
#include <proc/readproc.h>

double cal_porc_cpu_usage(proc_t *last_proc_ptr, proc_t *now_proc_ptr, Cpu_Time *last_cputime_ptr, Cpu_Time *now_cputime_ptr)
{
    uint32_t process_time = now_proc_ptr->utime + now_proc_ptr->stime - last_proc_ptr->utime - last_proc_ptr->stime;
    double cpu_total_time = now_cputime_ptr->cpu_all.total_time - last_cputime_ptr->cpu_all.total_time;
    return process_time / cpu_total_time * 100 * now_cputime_ptr->cpu_num;
}

int main(int argc, char* argv[]) {
    if (argc != 2) {
        fprintf(stderr, "Usage: %s <PID>\n", argv[0]);
        return 1;
    }
    pid_t target_pid = atoi(argv[1]);
    proc_t task_proc[2];
    proc_t * last_proc_ptr, * now_proc_ptr;
    memset(task_proc, 0, sizeof(task_proc));

    // 1.第一次获取进程
    if (get_proc_stats(target_pid, &task_proc[0]) == NULL) {
        fprintf(stderr, "Failed to get process information for PID %d\n", target_pid);
        return 1;
    }
    last_proc_ptr = NULL;
    now_proc_ptr = &task_proc[0];

    // 2.1 初始化读取CPU时间
    Cpu_Time* cpu_time[2];
    uint64_t count = 0, idx = 0;
    Cpu_Time* last_cputime_ptr, * now_cputime_ptr;
    if (init_cpu_time(&cpu_time[0]) == NULL || init_cpu_time(&cpu_time[1]) == NULL)
    {
        return -1;
    }
    int ret;
     // 2.2 第一次获取CPU时间
    ret = get_cpu_time(cpu_time[0]);
    if (ret != 0)
    {
        perror("get_cpu_time failed");
        return ret;
    }
    last_cputime_ptr = NULL;
    now_cputime_ptr = cpu_time[0];

    double proc_cpu_usage;
    while(1)
    {
        sleep(1);
        count++;
        idx = count % 2;

        // 3.下次获取进程cpu
        if (get_proc_stats(target_pid, &task_proc[idx]) == NULL) {
            fprintf(stderr, "Failed to get process information for PID %d\n", target_pid);
            return 1;
        }
        last_proc_ptr = now_proc_ptr;
        now_proc_ptr = &task_proc[idx];

        // 4.下次获取CPU时间
        ret = get_cpu_time(cpu_time[idx]);
        if (ret != 0)
        {
            perror("get_cpu_time failed");
            return ret;
        }
        last_cputime_ptr = now_cputime_ptr;
        now_cputime_ptr = cpu_time[idx];

        // 5.计算进程cpu使用率
        proc_cpu_usage = cal_porc_cpu_usage(last_proc_ptr, now_proc_ptr, last_cputime_ptr, now_cputime_ptr);
        printf("进程占用cpu: %.2f%%\n", proc_cpu_usage);
    }

    free_cpu_time(cpu_time[0]);
    free_cpu_time(cpu_time[1]);

    return 0;
}
